package com.aibaixun.common.utils.file;


import net.coobird.thumbnailator.Thumbnails;
import org.apache.commons.io.FileUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;


/**
 * @author zhangyh
 * @date 2022-09-19
 */

public class ThumbnailUtis {

    private static final Logger log = LoggerFactory.getLogger(ThumbnailUtis.class);

    /**
     * 根据指定大小压缩图片
     *
     * @param imageBytes  源图片字节数组
     * @param desFileSize 指定图片大小，单位kb
     * @param imageId     影像编号
     * @return 压缩质量后的图片字节数组
     */
    public static byte[] compressPictureForScale(byte[] imageBytes, long desFileSize, String imageId) {
        if (imageBytes == null || imageBytes.length <= 0 || imageBytes.length < desFileSize * 1024) {
            return imageBytes;
        }
        long srcSize = imageBytes.length;
        double accuracy = getAccuracy(srcSize / 1024);
        try {
            int i=0;
            long begin = System.currentTimeMillis();
            while (imageBytes.length > desFileSize * 1024) {
                ByteArrayInputStream inputStream = new ByteArrayInputStream(imageBytes);
                ByteArrayOutputStream outputStream = new ByteArrayOutputStream(imageBytes.length);
                Thumbnails.of(inputStream).scale(accuracy).outputQuality(accuracy).toOutputStream(outputStream);
                imageBytes = outputStream.toByteArray();
                log.info("第{}次压缩",i++);
            }
            log.info("【图片压缩】imageId={} | 图片原大小={}kb | 压缩后大小={}kb | 耗时：{}秒", imageId, srcSize / 1024, imageBytes.length / 1024,(System.currentTimeMillis() - begin)/1000);
        } catch (Exception e) {
            log.error("图片压缩失败!{}", e);
        }

        return imageBytes;
    }

    /**
     * 自动调节精度(经验数值)
     *
     * @param size 源图片大小
     * @return 图片压缩质量比
     */
    private static double getAccuracy(long size) {
        double accuracy;
        if (size < 900) {
            accuracy = 0.85;
        } else if (size < 2047) {
            accuracy = 0.6;
        } else if (size < 3275) {
            accuracy = 0.44;
        } else {
            accuracy = 0.4;
        }
        return accuracy;
    }

    public static void main(String[] args) throws IOException {
        File file = new File("D:\\home\\8dc5eaff6fa6a158a1bf62be06d61cd.jpg");
        File desc = new File("D:\\home\\a1.jpg");
        //将文件内容读入字节数组。文件始终处于关闭状态。
        byte[] bytes = FileUtils.readFileToByteArray(file);
        long begin = System.currentTimeMillis();
        bytes = ThumbnailUtis.compressPictureForScale(bytes, 200, "x");
        log.info("压缩结束，耗时：{}",(System.currentTimeMillis() - begin)/1000);
        //将字节数组写入到文件
        FileUtils.writeByteArrayToFile(desc, bytes);
    }
}
